package com.aokang.footwear.common.enums;

import com.aokang.footwear.common.i18n.IErrorCodeEnum;
import lombok.AllArgsConstructor;
import lombok.Getter;

import java.util.stream.Stream;

/**
 * @author chil
 */
@AllArgsConstructor
public enum ErrorCodeEnum implements IErrorCodeEnum {
    //-------------------------通用错误码-------------------------
    SUCCESS(200, "success"),
    UNKNOWN_ERROR(500, "发生了未知的错误，请联系客服处理"),
    USER_REPEAT(1000, "用户账号重复"),
    ROLE_REPEAT(1001, "角色重复"),
    PARAM_ILLEGAL(1002, "参数错误"),
    REQUEST_REPEAT_SUBMIT(1003, "操作太频繁，请稍后再试"),
    TIME_FORMAT_ERROR(1004, "时间格式错误"),
    UPLOAD_FILE_ERROR(1005, "上传的文件错误"),
    ROLE_NOT_EXIST(1006, "角色不存在"),
    UPLOAD_BIZ_CODE_IS_NULL(1007, "文件上传类型不存在"),
    UPLOAD_FILE_FAIL(1008, "上传失败"),
    USER_NOT_EXIST(1009, "用户不存在"),
    RECORD_ALREADY_EXISTS(3002, "数据库中已存在该记录"),
    DATA_ERROR(3003, "数据错误"),
    TOKEN_TIMEOUT(4001, "未登录或登录超时，请重新登录"),
    LOGIN_ERROR(4002, "账号或密码错误"),

    //-------------------------业务错误码-------------------------
    ;

    public final int code;
    public final String msg;

    @Override
    public Integer getCode() {
        return code;
    }

    @Override
    public String getMsg() {
        return msg;
    }

    /**
     * 返回动态错误对象（包含动态的 msg）
     *
     * @param args 格式化参数
     * @return 包装后的动态错误对象
     */
    public DynamicErrorCode format(Object... args) {
        String formattedMsg = String.format(this.msg, args);
        return new DynamicErrorCode(this.code, formattedMsg);
    }

    /**
     * 返回动态错误对象（添加前缀到 msg）
     *
     * @param prefix 前缀
     * @return 包装后的动态错误对象
     */
    public DynamicErrorCode insert(String prefix) {
        String modifiedMsg = prefix + " " + this.msg;
        return new DynamicErrorCode(this.code, modifiedMsg);
    }

    /**
     * 动态错误包装类
     */
    @AllArgsConstructor
    @Getter
    public static class DynamicErrorCode implements IErrorCodeEnum {
        private final int code;
        private final String msg;

        @Override
        public Integer getCode() {
            return code;
        }

        @Override
        public String getMsg() {
            return msg;
        }
    }

    public static ErrorCodeEnum getByCode(Integer code) {
        return Stream.of(values()).filter(o -> o.getCode().equals(code)).findFirst().orElse(null);
    }
}
